package cn.easier.activity.console.service.impl;

import cn.easier.activity.console.repository.ActivityInfoRepository;
import cn.easier.activity.console.repository.ActivityPrizeRepository;
import cn.easier.activity.console.repository.ActivityRecordRepository;
import cn.easier.activity.console.service.ActivityGuessService;
import cn.easier.activity.web.entity.ActivityInfo;
import cn.easier.activity.web.entity.ActivityPrize;
import cn.easier.activity.web.entity.ActivityRecord;
import cn.easier.club.base.dto.ResultInfo;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import org.apache.commons.lang.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.Date;
import java.util.HashSet;
import java.util.List;
import java.util.Optional;

/**
 * 活动信息ServiceImpl
 */
@Service
@Transactional
public class ActivityGuessServiceImpl implements ActivityGuessService {

    private static Logger logger = LoggerFactory.getLogger(ActivityGuessServiceImpl.class);

    private final ActivityInfoRepository activityInfoRepository;
    private final ActivityPrizeRepository activityPrizeRepository;
    private final ActivityRecordRepository activityRecordRepository;

    public ActivityGuessServiceImpl(ActivityInfoRepository activityInfoRepository, ActivityPrizeRepository activityPrizeRepository, ActivityRecordRepository activityRecordRepository) {
        this.activityInfoRepository = activityInfoRepository;
        this.activityPrizeRepository = activityPrizeRepository;
        this.activityRecordRepository = activityRecordRepository;
    }

    @Override
    public ResultInfo guessLottery(Integer activityId, String type) {
        logger.info("竞猜定时开奖任务, activityInfoId: {}", activityId);
        Optional<ActivityInfo> optionalActivityInfo = activityInfoRepository.findById(activityId);
        if (!optionalActivityInfo.isPresent()) {
            logger.info("当前活动不存在");
            return new ResultInfo("ERROR", "当前活动不存在", null);
        }
        if (!optionalActivityInfo.get().getTypeIdentification().equals("tournamentguess")) {
            logger.info("活动类型不对，无法开奖");
            return new ResultInfo("ERROR", "活动类型不对，无法开奖", null);
        }
        List<ActivityPrize> activityPrizeList = activityPrizeRepository.findAllByActivityInfoId(activityId);
        if (activityPrizeList.size() != 1) {
            logger.info("奖品设置有误，无法开奖");
            return new ResultInfo("ERROR", "奖品设置有误，无法开奖", null);
        }
        ActivityInfo activityInfo = optionalActivityInfo.get();
        if (activityInfo.getStatus() != 1 || !activityInfo.isReleaseFlag()) {
            logger.info("活动状态有误，无法开奖");
            return new ResultInfo("ERROR", "活动状态有误，无法开奖", null);
        }
        Date date = new Date();
        Date endTime = activityInfo.getEndTime();
        if (endTime.after(date)) {
            logger.info("不能开奖结束时间没到{},活动ID是{}", endTime, activityInfo.getId());
            return new ResultInfo("ERROR", "不能开奖结束时间没到无法开奖", null);
        }
        String advancedSetting = activityInfo.getAdvancedSetting();
        JSONObject advancedConfigJson;
        if (StringUtils.isNotBlank(advancedSetting)) {
            advancedConfigJson = JSON.parseObject(advancedSetting);
        } else {
            advancedConfigJson = new JSONObject();
        }
        advancedConfigJson = JSON.parseObject(advancedSetting);
        Boolean finished = null;
        finished = advancedConfigJson.getBoolean("finished");
        if (finished != null) {
            if (finished) {
                logger.info("活动已经开奖，请勿重复开奖");
                return new ResultInfo("ERROR", "活动已经开奖，请勿重复开奖", null);
            }
        }
        // 查询用户参与记录
        List<ActivityRecord> activityRecordList = activityRecordRepository.findByActivityId(activityId);
        int platformPercent = advancedConfigJson.getIntValue("platformPercent");
        int baseIntegral = advancedConfigJson.getIntValue("baseIntegral");
        if (platformPercent <= 0 || platformPercent >= 100) {
            logger.info("平台扣除积分比例：{}，数值有误不扣除", platformPercent);
        }

        int totalIntegral = 0;
        int topic1Count = 0, topic2Count = 0;
        int totalCount = activityRecordList.size();
        HashSet<String> topic1Phone = new HashSet<>();
        HashSet<String> topic2Phone = new HashSet<>();
        for (ActivityRecord activityRecord : activityRecordList) {
            totalIntegral += activityRecord.getConsumeScore();
            if ("1".equalsIgnoreCase(activityRecord.getRemark())) {
                topic1Count++;
                topic1Phone.add(activityRecord.getPhoneNum());
            } else {
                topic2Count++;
                topic2Phone.add(activityRecord.getPhoneNum());
            }
        }
        float topic1Rate, topic2Rate;
        if (totalCount > 0) {
            topic1Rate = 100f * topic1Count / totalCount;
            if (topic1Rate == 50) {
                // 参与次数相同则比较人数
                if (topic1Phone.size() != topic2Phone.size()) {
                    topic1Rate = 100f * topic1Phone.size() / totalCount;
                }
            }
        } else {
            topic1Rate = 50;
        }
        // 避免 50.1 -- 49.9 展示为 50 -- 50
        if (topic1Rate < 50 && topic1Rate > 49) {
            topic1Rate = 49;
        }
        if (topic1Rate > 50 && topic1Rate < 51) {
            topic1Rate = 51;
        }
        // 避免 99.9 -- 0.1 展示为 100 -- 0
        if (topic1Rate < 1) {
            topic1Rate = 1;
        }
        if (topic1Rate > 99) {
            topic1Rate = 99;
        }
        topic2Rate = 100 - topic1Rate;
        double integral;
        long finalIntegral = Math.round(totalIntegral * (1f - 1f * platformPercent / 100f));
        if (type.equals("left")) {
            integral = 1D * finalIntegral / topic1Count;
        } else if (type.equals("right")) {
            integral = 1D * finalIntegral / topic2Count;
        } else {
            return new ResultInfo("ERROR", "不知道哪边获胜，无法开奖", null);
        }
        logger.info("总参与人数：{}，总积分数：{}，平台扣除比例：{}%，获胜方：{}，左侧人数：{}，右侧人数：{}，每次得到积分：{}",
                totalCount, totalIntegral, platformPercent, type, topic1Count, topic2Count, integral);
        // 标识已结算完成
        advancedConfigJson.put("finished", false);
        advancedConfigJson.put("topic1Count", Math.round(topic1Count));
        advancedConfigJson.put("topic2Count", Math.round(topic2Count));
        advancedConfigJson.put("topic1Rate", Math.round(topic1Rate));
        advancedConfigJson.put("topic2Rate", Math.round(topic2Rate));
        advancedConfigJson.put("totalIntegral", baseIntegral + totalIntegral);
        advancedConfigJson.put("win", type);
        advancedConfigJson.put("integral", integral);
        activityInfo.setAdvancedSetting(advancedConfigJson.toJSONString());
        activityInfoRepository.save(activityInfo);
        logger.info("开奖结束");
        return new ResultInfo("SUCCESS", "已经开奖请等待积分下发", null);
    }
}
